package com.xiaojie.service.order.impl;

import com.alibaba.csp.sentinel.Entry;
import com.alibaba.csp.sentinel.SphU;
import com.alibaba.csp.sentinel.annotation.SentinelResource;
import com.alibaba.csp.sentinel.slots.block.BlockException;
import com.xiaojie.service.order.feign.MemberServiceFeign;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@Slf4j
public class OrderService {
    @Autowired
    private MemberServiceFeign memberServiceFeign;
    // 限流规则名称
    private static final String GETORDER_KEY = "orderToMember";

    /**
     * 基于我们的fegin客户端形式实现rpc远程调用
     *
     * @return
     */
    @RequestMapping("/orderFeignToMember")
    public String orderFeignToMember() {
        String result = memberServiceFeign.getUser(1);
        return "我是订单服务调用会员服务的接口,返回结果" + result;
    }

    @RequestMapping("/")
    public String order() {
        return "订单服务";
    }

    @RequestMapping("/orderToMember")
    public String orderToMember() {
        Entry entry = null;
        try {
            entry = SphU.entry(GETORDER_KEY);
            return "orderToMember接口";
        } catch (Exception e) {
            // 限流的情况就会进入到Exception
            return "当前访问人数过多，请稍后重试!";
        } finally {
            // SphU.entry(xxx) 需要与 entry.exit() 成对出现,否则会导致调用链记录异常
            if (entry != null) {
                entry.exit();
            }
        }


    }

   /*
    *
    * fallback 服务降级后执行的办法
    * blockHandler 限流/熔断出现异常执行的方法
    * value 指定我们的资源的名称（配置的资源名）
    * @author xiaojie
    * @date 2021/6/17 9:36
    * @return java.lang.String
    */
    @SentinelResource(value = GETORDER_KEY, blockHandler = "getOrderQpsException")
    @RequestMapping("/orderToMemberSentinelResource")
    public String orderToMemberSentinelResource() {
        return "orderToMemberSentinelResource";
    }

    /*
     * @param e
     * @限流后返回的提示
     * @author xiaojie
     * @date 2021/6/17 9:38
     * @return java.lang.String
     */
    public String getOrderQpsException(BlockException e) {
        e.printStackTrace();
        return "该接口已经被限流啦!";
    }


    /**
     * 服务降级 限流、熔断、接口超时、接口出现异常
     */

    /**
     * 基于我们的控制创建规则实现限流
     *
     * @return
     */
    @SentinelResource(value = "getOrderConsole", blockHandler = "getOrderQpsException")
    @RequestMapping("/getOrderConsole")
    public String getOrderConsole() {
        return "getOrderConsole";
    }


    @SentinelResource(value = "getOrderSemaphore", blockHandler = "getOrderQpsException")
    @RequestMapping("/getOrderSemaphore")
    public String getOrderSemaphore() {
        try {
            Thread.sleep(500);
        } catch (Exception e) {

        }
        log.info(Thread.currentThread().getName());
        return "getOrderSemaphore";
    }
    /**
     * 注意：如果没有使用 @SentinelResource注解的情况下 默认的资源名称为接口路径地址
     */

    /**
     * @Description:调用服务降级的方法
     * @Author: yan
     * @Date: 2021/5/30 22:40
     * @return: java.lang.String
     **/
    @SentinelResource(value = "getOrderSentinel", blockHandler = "getOrderQpsException")
    @RequestMapping("/getOrderSentinel")
    public String getOrderSentinel() {
        try{
            Thread.sleep(300);
        }catch (Exception e){
            e.printStackTrace();
        }
        return "getOrderSentinel";
    }

}
